package jaoso.framework.dao.hibernate;

import jaoso.framework.dao.AccountDAO;
import jaoso.framework.dao.BaseDAO;
import jaoso.framework.dao.MyQuery;

import jaoso.framework.domain.Account;
import jaoso.framework.domain.Role;

import jaoso.framework.exception.DAOException;

import jaoso.framework.util.MyUtils;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import java.io.Serializable;

/**
 * @author Administrator
 * @version 0.9.1
 * @since 2004-5-29 Account DAO, persistent Account.
 */
public class AccountDAOImpl implements AccountDAO
{
    /** log */
    private static Log log = LogFactory.getLog(AccountDAOImpl.class);

    /** base dao */
    private BaseDAO baseDAO;

    /**
     * Creates a new AccountDAOImpl object.
     */
    public AccountDAOImpl()
    {
        super();
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#getAccount(java.io.Serializable)
     */
    public final Account getAccount(final Serializable id)
    {
        return (Account) baseDAO.loadEntity(Account.class, id);
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#getAccountByName(java.lang.String)
     */
    public final Account getAccountByName(final String name)
    {
        if (MyUtils.isBlank(name))
        {
            return null;
        }

        Account[] accounts = findAccount("from Account a where a.name='" + name
                + "' order by a.name");

        if (MyUtils.isBlank(accounts))
        {
            return null;
        }

        return accounts[0];
    }

    /**
     * @param dao
     *            dao
     */
    public final void setBaseDAO(final BaseDAO dao)
    {
        this.baseDAO = dao;
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#isExist(java.lang.String)
     */
    public final boolean isExist(final String name)
    {
        boolean flage = false;

        if (MyUtils.isBlank(name))
        {
            return flage;
        }

        try
        {
            //flage = getAccountByName(name) != null;
            flage = ((Integer) baseDAO
                    .findEntity("select count(*) from Account a where a.name='"
                            + name + "'")[0]).intValue() > 0;
        } catch (DAOException e)
        {
            log.error("account isExist error: ", e);
        }

        return flage;
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#isExist(java.lang.String,
     *      java.io.Serializable)
     */
    public final boolean isExist(final String name, final Serializable id)
    {
        boolean flage = false;

        if (MyUtils.isBlank(name) || (id == null))
        {
            return flage;
        }

        try
        {
            Account account = getAccountByName(name);
            flage = (account != null) && !account.getId().equals(id);
            flage = ((Integer) baseDAO
                    .findEntity("select count(*) from Account a where a.name='"
                            + name + "' and a.id<>'" + id + "'")[0]).intValue() > 0;
        } catch (DAOException e)
        {
            log.error("account isExist error: ", e);
        }

        return flage;
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#createAccount(jaoso.framework.domain.Account)
     */
    public final void createAccount(final Account account)
    {
        baseDAO.saveEntity(account);
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#findAccount(java.lang.String)
     */
    public final Account[] findAccount(final String query)
    {
        MyQuery myquery = new MyQuery();
        myquery.setQueryString(query);

        return findAccount(myquery);
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#findAccount(jaoso.framework.dao.MyQuery)
     */
    public final Account[] findAccount(final MyQuery query)
    {
        Object[] os = baseDAO.findEntity(query);

        if (MyUtils.isBlank(os))
        {
            return null;
        }

        Account[] entitys = new Account[os.length];
        System.arraycopy(os, 0, entitys, 0, os.length);

        return entitys;
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#findAllAccount()
     */
    public final Account[] findAllAccount()
    {
        return findAccount("from Account a order by a.name");
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#removeAccount(jaoso.framework.domain.Account)
     */
    public final void removeAccount(final Account account)
    {
        if (account.getGroup() != null)
        {
            Role group = account.getGroup();
            group.getAccounts().remove(account);
            baseDAO.updateEntity(group);
            account.setGroup(null);
        }

        baseDAO.removeEntity(account);
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#removeAccount(java.io.Serializable)
     */
    public final void removeAccount(final Serializable id)
    {
        if (id == null)
        {
            throw new DAOException("id can't be null");
        }

        removeAccount(getAccount(id));
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#removeAccount(java.io.Serializable[])
     */
    public final void removeAccount(final Serializable[] ids)
    {
        if (ids == null)
        {
            throw new DAOException("id can't be null");
        }

        for (int i = 0, n = ids.length; i < n; i++)
        {
            removeAccount(getAccount(ids[i]));
        }
    }

    /**
     * (non-Javadoc)
     * 
     * @see jaoso.framework.dao.AccountDAO#updateAccount(jaoso.framework.domain.Account)
     */
    public final void updateAccount(final Account account)
    {
        baseDAO.updateEntity(account);
    }
}